﻿namespace Pyramid.Hardware
{
	using System.Collections.Generic;
	using Pyramid.Utility;

	public class AsynchronousCounter
	{
		public AsynchronousCounter(int busSize, ILine clock, ILine resetLine)
		{
			Validate.IsGreaterThanZero(busSize, "size");

			var outputBus = new List<ILine>();

			var currentClockLine = clock;

			for (int lineIndex = 0; lineIndex < busSize; lineIndex++)
			{
				var newFlipFlop = CreateLoopbackFlipFlop(currentClockLine);

				outputBus.Add(newFlipFlop.Q);

				currentClockLine = newFlipFlop.QDown;
			}

			this.OutputBus = outputBus;
		}

		private static DFlipFlop CreateLoopbackFlipFlop(ILine clock)
		{
			var loopbackLine = new LineLink(FixedInputLine.Unknown);

			var newFlipFlop = new DFlipFlop(loopbackLine, clock);

			loopbackLine.InputLine = newFlipFlop.QUp;

			return newFlipFlop;
		}

		public IEnumerable<ILine> OutputBus
		{
			get;
			private set;
		}
	}
}
